﻿#ifndef OPCUA_QTHREAD_H
#define OPCUA_QTHREAD_H

#include <QThread>
#include <QVector>
#include <QString>
#include <QMutex>
#include <QQueue>
#include <QWaitCondition>
#include <QMap>
#include <QVariant>
#include "open62541.h"
#include <QMetaType>

//前置声明结构体
struct OpcUA_QThread_Task;

class OpcUA_QThread : public QThread
{
    Q_OBJECT
public:
    explicit OpcUA_QThread(QObject *parent = nullptr);
    ~OpcUA_QThread() override;

    //OPC UA初始化
    void init(const QString& endpointUrl);

    //阀门操作接口
    void readValveStatus(int valveChannel);
    void readAllValveStatus();
    void writeValveStatus(int valveChannel, bool status);
    void writeAllValveStatus(const QVector<bool>& status);

    //流量计操作接口
    void readFlowRate(int flowmeterChannel);
    void readAllFlowRate();
    void writeFlowRate(int flowmeterChannel, int16_t inputValue);
    void writeAllFlowRate(const QVector<int16_t>& inputValue);

    //压力计操作接口
    void readPressure(int pressuremeterChannel);
    void readAllPressure();
    void writePressure(int pressuremeterChannel, int16_t inputValue);
    void writeAllPressure(const QVector<int16_t>& inputValue);

    //MKS设备操作接口
    void readMKS();
    void writeMKS(int16_t pressure, int16_t openingAmplitude, int16_t switchMode);

    //温度设备操作接口
    void readTemperature();
    void writeTemperature(bool status1, bool status2, int16_t temperature1, int16_t temperature2);

    //其他设备操作接口
    void readOtherValveStatus(int valveChannel);
    void readOtherDataValue(int dataChannel);

    //定制型读取接口(HomePage界面使用)
    void readDataToHomePage();
    //定制型写入接口(HomePage界面使用)
    void writeDataFromHomePage(const QVector<int16_t>& flowValues, const QVector<int16_t>& pressureValues, const QVector<bool>& valves);

signals:
    //初始化结果信号
    void signals_initResult(bool success);

    //阀门操作结果信号
    void signals_valveStatusRead(int channel, bool result, bool success);
    void signals_allValveStatusRead(const QVector<bool>& result, bool success);
    void signals_valveStatusWritten(int channel, bool success);
    void signals_allValveStatusWritten(bool success);

    //流量计操作结果信号
    void signals_flowRateRead(int channel, int16_t result, bool success);
    void signals_allFlowRateRead(const QVector<int16_t>& result, bool success);
    void signals_flowRateWritten(int channel, bool success);
    void signals_allFlowRateWritten(bool success);

    //压力计操作结果信号
    void signals_pressureRead(int channel, int16_t result, bool success);
    void signals_allPressureRead(const QVector<int16_t>& result, bool success);
    void signals_pressureWritten(int channel, bool success);
    void signals_allPressureWritten(bool success);

    //MKS设备操作结果信号
    void signals_mksRead(int16_t pressure, int16_t openingAmplitude, bool success);
    void signals_mksWritten(bool success);

    //温度设备操作结果信号
    void signals_temperatureRead(int16_t temperature1, int16_t temperature2, bool success);
    void signals_temperatureWritten(bool success);

    //其他设备操作结果信号
    void signals_otherValveStatusRead(int channel, bool result, bool success);
    void signals_otherDataValueRead(int channel, int16_t result, bool success);

    //定制型读取接口信号(HomePage界面使用)
    void signals_sendDataToHomePage(QVector<int16_t> flowmeter, QVector<int16_t> pressuremeter, QVector<bool> valve, QVector<int16_t> temperature, int32_t dintPressure, bool success);
    void signals_dataFromHomePageWritten(bool Success);

protected:
    void run() override;

private:
    //任务结构体定义
    struct OpcUA_QThread_Task {
        enum Type {
            Init,
            ReadValveStatus,
            ReadAllValveStatus,
            WriteValveStatus,
            WriteAllValveStatus,
            ReadFlowRate,
            ReadAllFlowRate,
            WriteFlowRate,
            WriteAllFlowRate,
            ReadPressure,
            ReadAllPressure,
            WritePressure,
            WriteAllPressure,
            ReadMKS,
            WriteMKS,
            ReadTemperature,
            WriteTemperature,
            ReadOtherValveStatus,
            ReadOtherDataValue,
            readDataToHomePage,
            WriteDataFromHomePage
        };

        Type type;
        QString endpointUrl;
        int channel;
        bool boolValue;
        int16_t int16Value;
        QVector<bool> boolVector;
        QVector<int16_t> int16Vector;
        QVector<int16_t> int16Vector2;
        int16_t mksPressure;
        int16_t mksOpening;
        int16_t mksMode;
        bool tempStatus1;
        bool tempStatus2;
        int16_t temp1;
        int16_t temp2;
    };

    Open62541* m_client;          //OPC UA客户端实例
    QQueue<OpcUA_QThread_Task> m_tasks;  //任务队列
    QMutex m_mutex;               //线程安全锁
    QWaitCondition m_condition;   //任务等待条件
    bool m_running;               //线程运行状态

    //设备ID列表（仅在cpp中可见和初始化）
    static const QStringList s_valveID_OnlyRead;
    static const QStringList s_valveID_ReadAndWrite;
    static const QStringList s_otherValveID_OnlyRead;
    static const QStringList s_flowmeterID_OnlyRead;
    static const QStringList s_flowmeterID_ReadAndWrite;
    static const QStringList s_pressuremeterID_OnlyRead;
    static const QStringList s_pressuremeterID_ReadAndWrite;
    static const QStringList s_MKSID_OnlyRead;
    static const QStringList s_MKSID_ReadAndWrite;
    static const QStringList s_temperatureID_OnlyRead;
    static const QStringList s_temperatureID_ReadAndWrite;
    static const QStringList s_otherDataID_OnlyRead;
};

#endif // OPCUA_QTHREAD_H
